Stopwatch = function (listener,tempTime,param) {
    this.startTime = 0;
    this.stopTime = 0;
    this.totalElapsed = 0; // 总共运行的时间
    this.started = false;
    this.listener = (listener != undefined ? listener : null); //  执行方法
    this.tickResolution = 500; // 定时刷新时间间隔
    this.tickInterval = null;
    this.tempTime = (tempTime != undefined ? tempTime : 0);
    this.param = (param != undefined ? param : null);

    // * pretty static vars
    this.oneday = 1000 * 60 * 60 * 24;
    this.onehour = 1000 * 60 * 60;
    this.onemin = 1000 * 60;
    this.onesec = 1000;
}
Stopwatch.prototype.start = function () {
    var delegate = function (that, method) { return function () { return method.call(that) } };
    if (!this.started) {
        this.startTime = new Date().getTime() - this.tempTime;
        this.stopTime = 0;
        this.started = true;
        this.tickInterval = setInterval(delegate(this, this.onTick), this.tickResolution);
    }
}

Stopwatch.prototype.destory = function () {
    if (this.started) {     
        this.started = false;
        if (this.tickInterval != null)
            clearInterval(this.tickInterval);
    }
}

Stopwatch.prototype.restart = function () {
    this.stop();
    this.start();
}

Stopwatch.prototype.getElapsed = function () {
    // * if watch is stopped, use that date, else use now
    var elapsed = 0;
    // if (this.started) {

        elapsed = new Date().getTime() - this.tempTime;

        // elapsed = this.startTime;

    // }
    elapsed += this.totalElapsed;

    // var days = parseInt(elapsed / this.oneday);
    // elapsed %= this.oneday;
    var hours = parseInt(elapsed / this.onehour);
    elapsed %= this.onehour;
    var mins = parseInt(elapsed / this.onemin);
    elapsed %= this.onemin;
    var secs = parseInt(elapsed / this.onesec);
    var ms = elapsed % this.onesec;

    return {
        // days: days,
        hours: hours,
        minutes: mins,
        seconds: secs,
        milliseconds: ms
    };
}
Stopwatch.prototype.setElapsed = function (hours, mins, secs) {
    //	this.reset();
    this.totalElapsed = 0;
    this.startTime = new Date().getTime();
    this.stopTime = this.startTime;
    this.totalElapsed += hours * this.onehour;
    this.totalElapsed += mins * this.onemin;
    this.totalElapsed = Math.max(this.totalElapsed, 0); // * No negative numbers
    this.initialElapsed = this.totalElapsed;
    if (this.tickInterval != null) {
        var delegate = function (that, method) {
            return function () {
                return method.call(that);
            };
        };
        clearInterval(this.tickInterval);
        this.tickInterval = setInterval(delegate(this, this.onTick),
            this.tickResolution);
    }
}
Stopwatch.prototype.toString = function (milliseconds) {
    var milliseconds = milliseconds || false;
    var zpad = function (no, digits) {
        no = no.toString();
        while (no.length < digits)
            no = '0' + no;
        return no;
    }
    var e = this.getElapsed();
    // return zpad(e.days,2) + "天" + zpad(e.hours,2) + "小时" + zpad(e.minutes,2) + "分钟" + zpad(e.seconds,2) + (milliseconds ? '.' + zpad(e.milliseconds, 3) : '');
    // return zpad(e.days, 1) + "天" + zpad(e.hours, 1) + "小时" + zpad(e.minutes, 1) + "分钟" + zpad(e.seconds, 1) + "秒";
    return zpad(e.hours, 2) + ":" + zpad(e.minutes, 2) + ":" + zpad(e.seconds, 2);
}
Stopwatch.prototype.setListener = function (listener) {
    this.listener = listener;
}
// * triggered every <resolution> ms
Stopwatch.prototype.onTick = function () {
    if (this.listener != null) {
        this.listener(this,this.param);
    }
}

